package com.inventive.jmscache.server;

import com.inventive.jmscache.server.utils.CollectionEnumeration;
import com.inventive.jmscache.server.hazelcast.DataSerializationHelper;
import com.hazelcast.nio.DataSerializable;

import javax.jms.JMSException;
import javax.jms.MapMessage;
import java.io.Serializable;
import java.io.DataOutput;
import java.io.IOException;
import java.io.DataInput;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Map;

/**
 * Created by IntelliJ IDEA.
 */
public class JmsCacheMapMessage extends JmsCacheMessage implements MapMessage, Serializable, DataSerializable {

    private Map<String, Object> map = new HashMap<String, Object>();

    @Override
    public boolean getBoolean(String s) throws JMSException {
        return (Boolean)map.get(s);
    }

    @Override
    public byte getByte(String s) throws JMSException {
        return (Byte)map.get(s);
    }

    @Override
    public short getShort(String s) throws JMSException {
        return (Short)map.get(s);
    }

    @Override
    public char getChar(String s) throws JMSException {
        return (Character)map.get(s);
    }

    @Override
    public int getInt(String s) throws JMSException {
        return (Integer)map.get(s);
    }

    @Override
    public long getLong(String s) throws JMSException {
        return (Long)map.get(s);
    }

    @Override
    public float getFloat(String s) throws JMSException {
        return (Float)map.get(s);
    }

    @Override
    public double getDouble(String s) throws JMSException {
        return (Double)map.get(s);
    }

    @Override
    public String getString(String s) throws JMSException {
        return (String)map.get(s);
    }

    @Override
    public byte[] getBytes(String s) throws JMSException {
        return (byte[])map.get(s);
    }

    @Override
    public Object getObject(String s) throws JMSException {
        return map.get(s);
    }

    @Override
    public Enumeration getMapNames() throws JMSException {
        return new CollectionEnumeration<String>(map.keySet());
    }

    @Override
    public void setBoolean(String s, boolean b) throws JMSException {
        map.put(s, b);
    }

    @Override
    public void setByte(String s, byte b) throws JMSException {
        map.put(s, b);
    }

    @Override
    public void setShort(String s, short i) throws JMSException {
        map.put(s, i);
    }

    @Override
    public void setChar(String s, char c) throws JMSException {
        map.put(s, c);
    }

    @Override
    public void setInt(String s, int i) throws JMSException {
        map.put(s, i);
    }

    @Override
    public void setLong(String s, long l) throws JMSException {
        map.put(s, l);
    }

    @Override
    public void setFloat(String s, float v) throws JMSException {
        map.put(s, v);
    }

    @Override
    public void setDouble(String s, double v) throws JMSException {
        map.put(s, v);
    }

    @Override
    public void setString(String s, String s1) throws JMSException {
        map.put(s, s1);
    }

    @Override
    public void setBytes(String s, byte[] bytes) throws JMSException {
        map.put(s, bytes);
    }

    @Override
    public void setBytes(String s, byte[] bytes, int i, int i1) throws JMSException {
        throw new UnsupportedOperationException("Not implemented yet");
    }

    @Override
    public void setObject(String s, Object o) throws JMSException {
        map.put(s, o);
    }

    @Override
    public boolean itemExists(String s) throws JMSException {
        return map.containsKey(s);
    }

    @Override
    public void writeData(DataOutput dataOutput) throws IOException {
        super.writeData(dataOutput);
        if (map == null) {
            dataOutput.writeBoolean(true);
        } else {
            dataOutput.writeBoolean(false);
            dataOutput.writeInt(map.size());
            for (Map.Entry<String, Object> entry : map.entrySet()) {
                DataSerializationHelper.writeSafeUTF(dataOutput, entry.getKey());
                DataSerializationHelper.writeSafeObject(dataOutput, entry.getValue());
            }
        }
    }

    @Override
    public void readData(DataInput dataInput) throws IOException {
        super.readData(dataInput);
        if (!dataInput.readBoolean()) {
            int size = dataInput.readInt();
            map = new HashMap<String, Object>(size == 0 ? 8 : size);
            for (int x = 0 ; x< size; x++) {
                map.put(DataSerializationHelper.readSafeUTF(dataInput), DataSerializationHelper.readSafeObject(dataInput));
            }
        } else {
            map = null;
        }
    }
}
